home *** CD-ROM | disk | FTP | other *** search
/ Amiga Format CD 52 / Amiga Format AFCD52 (Issue 136, May 2000).iso / -serious- / programming / c / icu-1.3.1 / icu-bin / include / tblcoll.h < prev    next >
C/C++ Source or Header  |  2000-02-23  |  35KB  |  784 lines

  1. /*
  2. *******************************************************************************
  3. *                                                                             *
  4. * COPYRIGHT:                                                                  *
  5. *   (C) Copyright Taligent, Inc.,  1996                                       *
  6. *   (C) Copyright International Business Machines Corporation,  1996-1999     *
  7. *   Licensed Material - Program-Property of IBM - All Rights Reserved.        *
  8. *   US Government Users Restricted Rights - Use, duplication, or disclosure   *
  9. *   restricted by GSA ADP Schedule Contract with IBM Corp.                    *
  10. *                                                                             *
  11. *******************************************************************************
  12. *
  13. * File tblcoll.h
  14. *
  15. * Created by: Helena Shih
  16. *
  17. * Modification History:
  18. *
  19. *  Date        Name        Description
  20. *  2/5/97      aliu        Added streamIn and streamOut methods.  Added
  21. *                          constructor which reads RuleBasedCollator object from
  22. *                          a binary file.  Added writeToFile method which streams
  23. *                          RuleBasedCollator out to a binary file.  The streamIn
  24. *                          and streamOut methods use istream and ostream objects
  25. *                          in binary mode.
  26. *  2/12/97     aliu        Modified to use TableCollationData sub-object to
  27. *                          hold invariant data.
  28. *  2/13/97     aliu        Moved several methods into this class from Collation.
  29. *                          Added a private RuleBasedCollator(Locale&) constructor,
  30. *                          to be used by Collator::createDefault().  General
  31. *                          clean up.
  32. *  2/20/97     helena      Added clone, operator==, operator!=, operator=, and copy
  33. *                          constructor and getDynamicClassID.
  34. *  3/5/97      aliu        Modified constructFromFile() to add parameter
  35. *                          specifying whether or not binary loading is to be
  36. *                          attempted.  This is required for dynamic rule loading.
  37. * 05/07/97     helena      Added memory allocation error detection.
  38. *  6/17/97     helena      Added IDENTICAL strength for compare, changed getRules to 
  39. *                          use MergeCollation::getPattern.
  40. *  6/20/97     helena      Java class name change.
  41. *  8/18/97     helena      Added internal API documentation.
  42. * 09/03/97     helena      Added createCollationKeyValues().
  43. * 02/10/98     damiba      Added compare with "length" parameter
  44. * 08/05/98     erm         Synched with 1.2 version of RuleBasedCollator.java
  45. * 04/23/99     stephen     Removed EDecompositionMode, merged with
  46. *                          Normalizer::EMode
  47. * 06/14/99     stephen     Removed kResourceBundleSuffix
  48. *
  49. *******************************************************************************
  50. */
  51.  
  52. #ifndef TBLCOLL_H
  53. #define TBLCOLL_H
  54.  
  55. #include "utypes.h"
  56. #include "coll.h"
  57. #include "chariter.h"
  58. #include "unistr.h"
  59. #include "sortkey.h"
  60. #include "normlzr.h"
  61.  
  62. class VectorOfPToContractElement;
  63. class VectorOfInt;
  64. class VectorOfPToContractTable;
  65. class VectorOfPToExpandTable;
  66. class MergeCollation;
  67. class CollationElementIterator;
  68. class RuleBasedCollatorStreamer;
  69.  
  70. /**
  71.  * The RuleBasedCollator class provides the simple implementation of Collator,
  72.  * using data-driven tables.  The user can create a customized table-based
  73.  * collation.
  74.  * <P>
  75.  * RuleBasedCollator maps characters to collation keys.
  76.  * <p>
  77.  * Table Collation has the following restrictions for efficiency (other
  78.  * subclasses may be used for more complex languages) :
  79.  *       <p>1. If the French secondary ordering is specified in a collation object, 
  80.  *             it is applied to the whole object.
  81.  *       <p>2. All non-mentioned Unicode characters are at the end of the
  82.  *             collation order.
  83.  *       <p>3. Private use characters are treated as identical.  The private
  84.  *             use area in Unicode is 0xE800-0xF8FF.
  85.  * <p>The collation table is composed of a list of collation rules, where each
  86.  * rule is of three forms:
  87.  * <pre>
  88.  * .    < modifier >
  89.  * .    < relation > < text-argument >
  90.  * .    < reset > < text-argument >
  91.  * </pre>
  92.  * The following demonstrates how to create your own collation rules:
  93.  * <UL Type=round>
  94.  *    <LI><strong>Text Argument</strong>: A text argument is any sequence of
  95.  *        characters, excluding special characters (that is, whitespace
  96.  *        characters and the characters used in modifier, relation and reset).
  97.  *        If those characters are desired, you can put them in single quotes
  98.  *        (e.g. ampersand => '&').<P>
  99.  *    <LI><strong>Modifier</strong>: There is a single modifier,
  100.  *        which is used to specify that all secondary differences are
  101.  *        sorted backwards.
  102.  *        <p>'@' : Indicates that secondary differences, such as accents, are 
  103.  *                 sorted backwards, as in French.<P>
  104.  *    <LI><strong>Relation</strong>: The relations are the following:
  105.  *        <UL Type=square>
  106.  *            <LI>'<' : Greater, as a letter difference (primary)
  107.  *            <LI>';' : Greater, as an accent difference (secondary)
  108.  *            <LI>',' : Greater, as a case difference (tertiary)
  109.  *            <LI>'=' : Equal
  110.  *        </UL><P>
  111.  *    <LI><strong>Reset</strong>: There is a single reset,
  112.  *        which is used primarily for contractions and expansions, but which
  113.  *        can also be used to add a modification at the end of a set of rules.
  114.  *        <p>'&' : Indicates that the next rule follows the position to where
  115.  *            the reset text-argument would be sorted.
  116.  *
  117.  * <p>
  118.  * This sounds more complicated than it is in practice. For example, the
  119.  * following are equivalent ways of expressing the same thing:
  120.  * <pre>
  121.  * .    a < b < c
  122.  * .    a < b & b < c
  123.  * .    a < c & a < b
  124.  * </pre>
  125.  * Notice that the order is important, as the subsequent item goes immediately
  126.  * after the text-argument. The following are not equivalent:
  127.  * <pre>
  128.  * .    a < b & a < c
  129.  * .    a < c & a < b
  130.  * </pre>
  131.  * Either the text-argument must already be present in the sequence, or some
  132.  * initial substring of the text-argument must be present. (e.g. "a < b & ae <
  133.  * e" is valid since "a" is present in the sequence before "ae" is reset). In
  134.  * this latter case, "ae" is not entered and treated as a single character;
  135.  * instead, "e" is sorted as if it were expanded to two characters: "a"
  136.  * followed by an "e". This difference appears in natural languages: in
  137.  * traditional Spanish "ch" is treated as though it contracts to a single
  138.  * character (expressed as "c < ch < d"), while in traditional German "ä"
  139.  * (a-umlaut) is treated as though it expands to two characters (expressed as
  140.  * "a & ae ; ä < b").
  141.  * <p><strong>Ignorable Characters</strong>
  142.  * <p>For ignorable characters, the first rule must start with a relation (the
  143.  * examples we have used above are really fragments; "a < b" really should be
  144.  * "< a < b"). If, however, the first relation is not "<", then all the 
  145.  * text-arguments up to the first "<" are ignorable. For example, ", - < a < b"
  146.  * makes "-" an ignorable character, as we saw earlier in the word
  147.  * "black-birds". In the samples for different languages, you see that most
  148.  * accents are ignorable.
  149.  * <p><strong>Normalization and Accents</strong>
  150.  * <p>The Collator object automatically normalizes text internally to separate
  151.  * accents from base characters where possible. This is done both when
  152.  * processing the rules, and when comparing two strings. Collator also uses
  153.  * the Unicode canonical mapping to ensure that combining sequences are sorted
  154.  * properly (for more information, see <A HREF="http://www.aw.com/devpress">
  155.  * The Unicode Standard, Version 2.0</A>.)</P>
  156.  * <p><strong>Errors</strong>
  157.  * <p>The following are errors:
  158.  * <UL Type=round>
  159.  *     <LI>A text-argument contains unquoted punctuation symbols
  160.  *        (e.g. "a < b-c < d").
  161.  *     <LI>A relation or reset character not followed by a text-argument
  162.  *        (e.g. "a < , b").
  163.  *     <LI>A reset where the text-argument (or an initial substring of the
  164.  *         text-argument) is not already in the sequence.
  165.  *         (e.g. "a < b & e < f")
  166.  * </UL>
  167.  * <pre>
  168.  * .    Examples:
  169.  * .    Simple:     "< a < b < c < d"
  170.  * .    Norwegian:  "< a,A< b,B< c,C< d,D< e,E< f,F< g,G< h,H< i,I< j,J
  171.  * .                 < k,K< l,L< m,M< n,N< o,O< p,P< q,Q< r,R< s,S< t,T
  172.  * .                 < u,U< v,V< w,W< x,X< y,Y< z,Z
  173.  * .                 < å=a°,Å=A°
  174.  * .                 ;aa,AA< æ,Æ< ø,Ø"
  175.  * </pre>
  176.  * <p>To create a table-based collation object, simply supply the collation
  177.  * rules to the RuleBasedCollator contructor.  For example:
  178.  * <pre>
  179.  * .    UErrorCode status = U_ZERO_ERROR;
  180.  * .    RuleBasedCollator *mySimple = new RuleBasedCollator(Simple, status);
  181.  * </pre>
  182.  * <p>Another example:
  183.  * <pre>
  184.  * .    UErrorCode status = U_ZERO_ERROR;
  185.  * .    RuleBasedCollator *myNorwegian = new RuleBasedCollator(Norwegian, status);
  186.  * </pre>
  187.  * To add rules on top of an existing table, simply supply the orginal rules
  188.  * and modifications to RuleBasedCollator constructor.  For example,
  189.  * <pre>
  190.  * .     Traditional Spanish (fragment): ... & C < ch , cH , Ch , CH ...
  191.  * .     German (fragment) : ...< y , Y < z , Z
  192.  * .                         & AE, Ä & AE, ä 
  193.  * .                         & OE , Ö & OE, ö 
  194.  * .                         & UE , Ü & UE, ü 
  195.  * .     Symbols (fragment): ...< y, Y < z , Z
  196.  * .                         & Question-mark ; '?'
  197.  * .                         & Ampersand ; '&'
  198.  * .                         & Dollar-sign ; '$'
  199.  * <p>To create a collation object for traditional Spanish, the user can take
  200.  * the English collation rules and add the additional rules to the table.
  201.  * For example:
  202.  * <pre>
  203.  * .     UErrorCode status = U_ZERO_ERROR;
  204.  * .     UnicodeString rules(DEFAULTRULES);
  205.  * .     rules += "& C < ch, cH, Ch, CH";
  206.  * .     RuleBasedCollator *mySpanish = new RuleBasedCollator(rules, status);
  207.  * </pre>
  208.  * <p>In order to sort symbols in the similiar order of sorting their
  209.  * alphabetic equivalents, you can do the following,
  210.  * <pre>
  211.  * .     UErrorCode status = U_ZERO_ERROR;
  212.  * .     UnicodeString rules(DEFAULTRULES);
  213.  * .     rules += "& Question-mark ; '?' & Ampersand ; '&' & Dollar-sign ; '$' ";
  214.  * .     RuleBasedCollator *myTable = new RuleBasedCollator(rules, status);
  215.  * </pre>
  216.  * <p>Another way of creating the table-based collation object, mySimple,
  217.  * is:
  218.  * <pre>
  219.  * .     UErrorCode status = U_ZERO_ERROR;
  220.  * .     RuleBasedCollator *mySimple = new
  221.  * .           RuleBasedCollator(" < a < b & b < c & c < d", status);
  222.  * </pre>
  223.  * Or,
  224.  * <pre>
  225.  * .     UErrorCode status = U_ZERO_ERROR;
  226.  * .     RuleBasedCollator *mySimple = new
  227.  * .           RuleBasedCollator(" < a < b < d & b < c", status);
  228.  * </pre>
  229.  * Because " < a < b < c < d" is the same as "a < b < d & b < c" or
  230.  * "< a < b & b < c & c < d".
  231.  *
  232.  * <p>To combine collations from two locales, (without error handling for clarity)
  233.  * <pre>
  234.  * .    // Create an en_US Collator object
  235.  * .    Locale locale_en_US("en", "US", "");
  236.  * .    RuleBasedCollator* en_USCollator = (RuleBasedCollator*)
  237.  * .        Collator::createInstance( locale_en_US, success );
  238.  * .
  239.  * .    // Create a da_DK Collator object
  240.  * .    Locale locale_da_DK("da", "DK", "");
  241.  * .    RuleBasedCollator* da_DKCollator = (RuleBasedCollator*)
  242.  * .        Collator::createInstance( locale_da_DK, success );
  243.  * .
  244.  * .    // Combine the two
  245.  * .    // First, get the collation rules from en_USCollator
  246.  * .    UnicodeString rules = en_USCollator->getRules();
  247.  * .    // Second, get the collation rules from da_DKCollator
  248.  * .    rules += da_DKCollator->getRules();
  249.  * .    RuleBasedCollator* newCollator = new RuleBasedCollator( rules, success );
  250.  * .    // newCollator has the combined rules
  251.  * </pre>
  252.  * <p>Another more interesting example would be to make changes on an existing
  253.  * table to create a new collation object.  For example, add
  254.  * "& C < ch, cH, Ch, CH" to the en_USCollation object to create your own
  255.  * English collation object,
  256.  * <pre>
  257.  * .    // Create a new Collator object with additional rules
  258.  * .    rules = en_USCollator->getRules();
  259.  * .    rules += "& C < ch, cH, Ch, CH";
  260.  * .    RuleBasedCollator* myCollator = new RuleBasedCollator( rules, success );
  261.  * .    // myCollator contains the new rules
  262.  * </pre>
  263.  *
  264.  * <p>The following example demonstrates how to change the order of
  265.  * non-spacing accents,
  266.  * <pre>
  267.  * .     UChar contents[] = {
  268.  * .         '=', 0x0301, ';', 0x0300, ';', 0x0302,
  269.  * .         ';', 0x0308, ';', 0x0327, ',', 0x0303,    // main accents
  270.  * .         ';', 0x0304, ';', 0x0305, ';', 0x0306,    // main accents
  271.  * .         ';', 0x0307, ';', 0x0309, ';', 0x030A,    // main accents
  272.  * .         ';', 0x030B, ';', 0x030C, ';', 0x030D,    // main accents
  273.  * .         ';', 0x030E, ';', 0x030F, ';', 0x0310,    // main accents
  274.  * .         ';', 0x0311, ';', 0x0312,                 // main accents
  275.  * .         '<', 'a', ',', 'A', ';', 'a', 'e', ',', 'A', 'E',
  276.  * .         ';', 0x00e6, ',', 0x00c6, '<', 'b', ',', 'B',
  277.  * .         '<', 'c', ',', 'C', '<', 'e', ',', 'E', '&', 
  278.  * .         'C', '<', 'd', ',', 'D', 0 };
  279.  * .     UnicodeString oldRules(contents);
  280.  * .     UErrorCode status = U_ZERO_ERROR;
  281.  * .     // change the order of accent characters
  282.  * .     UChar addOn[] = { '&', ',', 0x0300, ';', 0x0308, ';', 0x0302, 0 };
  283.  * .     oldRules += addOn;
  284.  * .     RuleBasedCollator *myCollation = new RuleBasedCollator(oldRules, status);
  285.  * </pre>
  286.  *
  287.  * <p> The last example shows how to put new primary ordering in before the
  288.  * default setting. For example, in Japanese collation, you can either sort
  289.  * English characters before or after Japanese characters,
  290.  * <pre>
  291.  * .     UErrorCode status = U_ZERO_ERROR;
  292.  * .     // get en_US collation rules
  293.  * .     RuleBasedCollator* en_USCollation = 
  294.  * .         (RuleBasedCollator*) Collator::createInstance(Locale::US, status);
  295.  * .     // Always check the error code after each call.
  296.  * .     if (U_FAILURE(status)) return;
  297.  * .     // add a few Japanese character to sort before English characters
  298.  * .     // suppose the last character before the first base letter 'a' in
  299.  * .     // the English collation rule is 0x2212
  300.  * .     UChar jaString[] = { '&', 0x2212, '<', 0x3041, ',', 0x3042, '<', 0x3043, ',', 0x3044, 0 };
  301.  * .     UnicodeString rules( en_USCollation->getRules() );
  302.  * .     rules += jaString;
  303.  * .     RuleBasedCollator *myJapaneseCollation = new RuleBasedCollator(rules, status);
  304.  * </pre>
  305.  * <p><strong>NOTE</strong>: Typically, a collation object is created with
  306.  * Collator::createInstance().
  307.  * <p>
  308.  * <strong>Note:</strong> <code>RuleBasedCollator</code>s with different Locale,
  309.  * CollationStrength and Decomposition mode settings will return different
  310.  * sort orders for the same set of strings. Locales have specific 
  311.  * collation rules, and the way in which secondary and tertiary differences 
  312.  * are taken into account, for example, will result in a different sorting order
  313.  * for same strings.
  314.  * <p>
  315.  * @see        Collator
  316.  * @version    1.27 4/8/97
  317.  * @author     Helena Shih
  318.  */
  319. class U_I18N_API RuleBasedCollator : public Collator 
  320. {
  321. public : 
  322.  
  323.   // constructor/destructor
  324.   /**
  325.    * RuleBasedCollator constructor.  This takes the table rules and builds
  326.    * a collation table out of them.  Please see RuleBasedCollator class
  327.    * description for more details on the collation rule syntax.
  328.    * @see Locale
  329.    * @param rules the collation rules to build the collation table from.
  330.      */
  331.   RuleBasedCollator(  const   UnicodeString&  rules,
  332.               UErrorCode&      status);
  333.  
  334.   RuleBasedCollator(  const   UnicodeString&  rules,
  335.               ECollationStrength collationStrength,
  336.               UErrorCode&      status);
  337.  
  338.   RuleBasedCollator(  const   UnicodeString&  rules,
  339.               Normalizer::EMode decompositionMode,
  340.               UErrorCode&      status);
  341.  
  342.   RuleBasedCollator(  const   UnicodeString&  rules,
  343.               ECollationStrength collationStrength,
  344.               Normalizer::EMode  decompositionMode,
  345.               UErrorCode&      status);
  346.  
  347.   /** Destructor
  348.      */
  349.   virtual                         ~RuleBasedCollator();
  350.  
  351.  
  352.   /** Copy constructor
  353.      */
  354.   RuleBasedCollator(const RuleBasedCollator& other);
  355.  
  356.   /**
  357.      * Assignment operator.
  358.      */
  359.   RuleBasedCollator&      operator=(const RuleBasedCollator& other);
  360.     
  361.   /**
  362.      * Returns true if "other" is the same as "this".
  363.      */
  364.   virtual bool_t                  operator==(const Collator& other) const;
  365.  
  366.   /**
  367.      * Returns true if "other" is not the same as "this".
  368.      */
  369.   virtual bool_t                  operator!=(const Collator& other) const;
  370.  
  371.   /**
  372.      * Makes a deep copy of the object.  The caller owns the returned object.
  373.      * @return the cloned object.
  374.      */
  375.   virtual Collator*               clone(void) const;
  376.  
  377.   /**
  378.      * Creates a collation element iterator for the source string.  The 
  379.      * caller of this method is responsible for the memory management of 
  380.      * the return pointer.
  381.      * @param source the string over which the CollationElementIterator will iterate.
  382.      * @return the collation element iterator of the source string using this as
  383.      * the based collator.
  384.      */
  385.   virtual CollationElementIterator*       createCollationElementIterator(const UnicodeString& source) const;
  386.  
  387.   /**
  388.      * Creates a collation element iterator for the source.  The 
  389.      * caller of this method is responsible for the memory management of 
  390.      * the returned pointer.
  391.      * @param source the CharacterIterator which produces the characters over which the
  392.      * CollationElementItgerator will iterate.
  393.      * @return the collation element iterator of the source using this as
  394.      * the based collator.
  395.      */
  396.   virtual CollationElementIterator*       createCollationElementIterator(const CharacterIterator& source) const;
  397.  
  398.   /**
  399.      * Compares a range of character data stored in two different strings
  400.      * based on the collation rules.  Returns
  401.      * information about whether a string is less than, greater than or
  402.      * equal to another string in a language.
  403.      * This can be overriden in a subclass.
  404.      * @param source the source string.
  405.      * @param target the target string to be compared with the source stirng.
  406.      * @return the comparison result.  GREATER if the source string is greater
  407.      * than the target string, LESS if the source is less than the target.  Otherwise,
  408.      * returns EQUAL.
  409.      */
  410.   virtual     EComparisonResult   compare(    const   UnicodeString&  source, 
  411.                           const   UnicodeString&  target) const;
  412.         
  413.         
  414.   /**
  415.      * Compares a range of character data stored in two different strings
  416.      * based on the collation rules up to the specified length.  Returns
  417.      * information about whether a string is less than, greater than or
  418.      * equal to another string in a language.
  419.      * This can be overriden in a subclass.
  420.      * @param source the source string.
  421.      * @param target the target string to be compared with the source string.
  422.      * @param length compares up to the specified length
  423.      * @return the comparison result.  GREATER if the source string is greater
  424.      * than the target string, LESS if the source is less than the target.  Otherwise,
  425.      * returns EQUAL.
  426.      */ 
  427.   virtual     EComparisonResult   compare(    const   UnicodeString&  source, 
  428.                           const   UnicodeString&  target,
  429.                           int32_t length) const;
  430.  
  431.   /** Transforms a specified region of the string into a series of characters
  432.      * that can be compared with CollationKey.compare. Use a CollationKey when
  433.      * you need to do repeated comparisions on the same string. For a single comparison
  434.      * the compare method will be faster.
  435.      * @param source the source string.
  436.      * @param key the transformed key of the source string.
  437.      * @param status the error code status.
  438.      * @return the transformed key.
  439.      * @see CollationKey
  440.      */
  441.   virtual     CollationKey&       getCollationKey(    const   UnicodeString&  source,
  442.                               CollationKey&   key,
  443.                               UErrorCode&  status) const;
  444.   /**
  445.      * Generates the hash code for the rule-based collation object.
  446.      * @return the hash code.
  447.      */
  448.   virtual     int32_t             hashCode(void) const;
  449.  
  450.   /**
  451.      * Gets the table-based rules for the collation object.
  452.      * @return returns the collation rules that the table collation object
  453.      * was created from.
  454.      */
  455.   const       UnicodeString&      getRules(void) const;
  456.  
  457.   /**
  458.      *  Return the maximum length of any expansion sequences that end
  459.      *  with the specified comparison order.
  460.      * 
  461.      *  @param order a collation order returned by previous or next.
  462.      *  @return the maximum length of any expansion seuences ending
  463.      *          with the specified order.
  464.      * 
  465.      *  @see CollationElementIterator#getMaxExpansion
  466.      */
  467.   int32_t                getMaxExpansion(int32_t order) const;
  468.  
  469.   /**
  470.      * Returns a unique class ID POLYMORPHICALLY.  Pure virtual override.
  471.      * This method is to implement a simple version of RTTI, since not all
  472.      * C++ compilers support genuine RTTI.  Polymorphic operator==() and
  473.      * clone() methods call this method.
  474.      *
  475.      * @return          The class ID for this object. All objects of a
  476.      *                  given class have the same class ID.  Objects of
  477.      *                  other classes have different class IDs.
  478.      */
  479.   virtual UClassID getDynamicClassID(void) const
  480.     { return RuleBasedCollator::getStaticClassID(); }
  481.  
  482.  
  483.   /**
  484.      * Returns the class ID for this class.  This is useful only for
  485.      * comparing to a return value from getDynamicClassID().  For example:
  486.      *
  487.      *      Base* polymorphic_pointer = createPolymorphicObject();
  488.      *      if (polymorphic_pointer->getDynamicClassID() ==
  489.      *          Derived::getStaticClassID()) ...
  490.      *
  491.      * @return          The class ID for all objects of this class.
  492.      */
  493.   static UClassID getStaticClassID(void) { return (UClassID)&fgClassID; }
  494.  
  495.   /*****************************************************************************
  496.  * PRIVATE
  497.  *****************************************************************************/
  498. private:
  499.   static      char                fgClassID;
  500.  
  501.         // Streamer used to read/write binary collation data files.
  502.   friend        class                RuleBasedCollatorStreamer;
  503.  
  504.   // Used to iterate over collation elements in a character source.
  505.   friend      class               CollationElementIterator;
  506.         
  507.   // Collator ONLY needs access to RuleBasedCollator(const Locale&, UErrorCode&)
  508.   friend class Collator;
  509.         
  510.   // TableCollationData ONLY needs access to UNMAPPED
  511.   friend class TableCollationData;
  512.  
  513.  
  514.   /** Default constructor
  515.      */
  516.   RuleBasedCollator();
  517.  
  518.   /**
  519.      * Create a new entry in the expansion table that contains the orderings
  520.      * for the given characers.  If anOrder is valid, it is added to the
  521.      * beginning of the expanded list of orders.
  522.      */
  523.   int32_t                addExpansion(int32_t anOrder,
  524.                              const UnicodeString &expandChars);
  525.   /**
  526.      * Create a table-based collation object with the given rules.
  527.      * @see RuleBasedCollator#RuleBasedCollator
  528.      * @exception FormatException If the rules format is incorrect.
  529.      */
  530.   void                build(  const   UnicodeString&  rules,
  531.                   UErrorCode&      success);
  532.  
  533.   /** Add expanding entries for pre-composed unicode characters so that this
  534.      * collator can be used reasonably well with decomposition turned off.
  535.      */
  536.   void                addComposedChars(void);
  537.  
  538.   /**
  539.      * Look up for unmapped values in the expanded character table.
  540.      */
  541.   void                commit(void);
  542.   /**
  543.      * Increment of the last order based on the collation strength.
  544.      * @param s the collation strength.
  545.      * @param lastOrder the last collation order.
  546.      * @return the new collation order.
  547.      */
  548.   int32_t             increment(  Collator::ECollationStrength    s, 
  549.                   int32_t                         lastOrder);
  550.   /**
  551.      * Adds a character and its designated order into the collation table.
  552.      * @param ch the Unicode character,
  553.      * @param anOrder the order.
  554.      * @param status the error code status.
  555.      */
  556.   void                addOrder(   UChar        ch, 
  557.                   int32_t        anOrder, 
  558.                   UErrorCode&  status);
  559.   /**
  560.      * Adds the expanding string into the collation table, for example, a-umlaut in German.
  561.      * @param groupChars the contracting characters.
  562.      * @param expChars the expanding characters.
  563.      * @param anOrder the order.
  564.      * @param status the error code status.
  565.      */
  566.   void                addExpandOrder(const    UnicodeString&          groupChars, 
  567.                      const    UnicodeString&          expChars, 
  568.                      int32_t                            anOrder,
  569.                      UErrorCode&                       status);
  570.   /**
  571.      * Adds the contracting string into the collation table, for example, ch in Spanish.
  572.      * @param groupChars the contracting characters.
  573.      * @param anOrder the order.
  574.      * @param status the error code status.
  575.      */
  576.   void                addContractOrder(const  UnicodeString&          groupChars, 
  577.                        int32_t                        anOrder,
  578.                        UErrorCode&                     status);
  579.   /**
  580.      * Adds the contracting string into the collation table, for example, ch in Spanish.
  581.      * @param groupChars the contracting characters.
  582.      * @param anOrder the order.
  583.      * @param fwd TRUE if this is for the forward direction
  584.      * @param status the error code status.
  585.      */
  586.   void                addContractOrder(const  UnicodeString&          groupChars, 
  587.                        int32_t                        anOrder,
  588.                        bool_t                            fwd,
  589.                        UErrorCode&                     status);
  590.   /**
  591.      * If the given string has been specified as a contracting string
  592.      * in this collation table, return its ordering, otherwise return UNMAPPED.
  593.      * @param groupChars the string
  594.      * @return the order of the contracted character, or UNMAPPED if
  595.      * there isn't one.
  596.      */
  597.   int32_t                getContractOrder(const    UnicodeString            &groupChars) const;
  598.   /**
  599.      *  Gets the entry of list of the contracting string in the collation
  600.      *  table.
  601.      *  @param ch the starting character of the contracting string
  602.      *  @return the entry of contracting element which starts with the specified
  603.      *  character in the list of contracting elements.
  604.      */
  605.   VectorOfPToContractElement* 
  606.   getContractValues(UChar     ch) const;
  607.   /**
  608.    *  Ges the entry of list of the contracting string in the collation
  609.    *  table.
  610.    *  @param index the index of the contract character list
  611.    *  @return the entry of the contracting element of the specified index in the
  612.    *  list.
  613.      */
  614.   VectorOfPToContractElement* 
  615.   getContractValues(int32_t     index) const;
  616.   /**
  617.    *  Gets the entry of value list of the expanding string in the collation
  618.    *  table at the specified index.
  619.    *  @param order the order of the expanding string value list
  620.    *  @return the entry of the expanding-char element of the specified index in 
  621.    *  the list.
  622.      */
  623.   VectorOfInt*        getExpandValueList(int32_t     order) const;
  624.   /**
  625.      *  Gets the comarison order of a character from the collation table.
  626.      *  @param ch the Unicode character
  627.      *  @return the comparison order of a character.
  628.      */
  629.   int32_t             getUnicodeOrder(UChar     ch) const;
  630.  
  631.   /**
  632.      *  Gets the comarison order of a character from the collation table.
  633.      *  @param ch the Unicode character
  634.      *  @return the comparison order of a character.
  635.      */
  636.   int32_t                getCharOrder(UChar ch) const;
  637.  
  638.   /**
  639.      *  Gets the comarison order of a character from the collation table.
  640.      *  @param list the contracting element table.
  641.      *  @param name the contracting char string.
  642.      *  @return the comparison order of the contracting character.
  643.      */
  644.   static        int32_t             getEntry(   VectorOfPToContractElement*     list, 
  645.                         const   UnicodeString&          name,
  646.                         bool_t                    fwd);
  647.  
  648.   /**
  649.      * Flattens the given object persistently to a file.  The file name
  650.      * argument should be a path name that can be passed directly to the
  651.      * underlying OS.  Once a RuleBasedCollator has been written to a file,
  652.      * it can be resurrected by calling the RuleBasedCollator(const char*)
  653.      * constructor, which operates very quickly.
  654.      * @param fileName the output file name.
  655.      * @return TRUE if writing to the file was successful, FALSE otherwise.
  656.      */
  657.   bool_t              writeToFile(const char* fileName) const; // True on success
  658.  
  659.   /**
  660.      * Add this table collation to the cache.  This involves adding the
  661.      * enclosed TableCollationData to the cache, and then marking our
  662.      * pointer as "not owned" by setting dataIsOwned to false.
  663.      * @param key the unique that represents this collation data object.
  664.      */
  665.   void                addToCache(         const UnicodeString& key);
  666.  
  667.   /**
  668.      * RuleBasedCollator constructor.  This constructor takes a locale.  The only
  669.      * caller of this class should be Collator::createInstance().  If createInstance()
  670.      * happens to know that the requested locale's collation is implemented as
  671.      * a RuleBasedCollator, it can then call this constructor.  OTHERWISE IT SHOULDN'T,
  672.      * since this constructor ALWAYS RETURNS A VALID COLLATION TABLE.  It does this
  673.      * by falling back to defaults.
  674.      */
  675.   RuleBasedCollator(      const Locale& desiredLocale,
  676.               UErrorCode& status);
  677.   /**
  678.      * Internal constructFromXyx() methods.  These methods do object construction
  679.      * from various sources.  They act like assignment operators; whatever used
  680.      * to be in this object is discarded.  <P>FROM RULES.  This constructor turns
  681.      * around and calls build().  <P>FROM CACHE.  This constructor tries to get the
  682.      * requested cached TableCollationData object, and wrap us around it.  <P>FROM FILE.
  683.      * There are two constructors named constructFromFile().  One takes a const char*:
  684.      * this is a path name to be passed directly to the host OS, where a flattened
  685.      * table collation (produced by writeToFile()) resides.  The other method takes
  686.      * a Locale, and a UnicodeString locale file name.  The distinction is this:
  687.      * the Locale is the locale we are seeking.  The file name is the name of the
  688.      * data file (either binary, as produced by writeToFile(), or ASCII, as read
  689.      * by ResourceBundle).  Within the file, if it is found, the method will look
  690.      * for the given Locale.
  691.      */
  692.   void                constructFromRules( const UnicodeString& rules,
  693.                       UErrorCode& status);
  694.   void                constructFromFile(  const Locale&           locale,
  695.                       const UnicodeString&    localeFileName,
  696.                       bool_t                  tryBinaryFile,
  697.                       UErrorCode&              status);
  698.   void                constructFromFile(  const char* fileName,
  699.                       UErrorCode& status);
  700.   void                constructFromCache( const UnicodeString& key,
  701.                       UErrorCode& status);
  702.  
  703.   //--------------------------------------------------------------------------
  704.   // Internal Static Utility Methods
  705.   /**
  706.      * Creates the path name with given information.
  707.      * @param prefix the prefix of the file name.
  708.      * @param name the actual file name.
  709.      * @param suffix the suffix of the file name.
  710.      * @return the generated file name.
  711.      */
  712.   static  char*               createPathName( const UnicodeString&    prefix,
  713.                           const UnicodeString&    name,
  714.                           const UnicodeString&    suffix);
  715.  
  716.   /**
  717.      * Chops off the last portion of the locale name.  For example, from "en_US_CA"
  718.      * to "en_US" and "en_US" to "en".
  719.      * @param localeName the locale name.
  720.      */
  721.   static  void                chopLocale(UnicodeString&   localeName);
  722.  
  723.   //--------------------------------------------------------------------------
  724.   // Constants
  725.  
  726.   static  const   int32_t             UNMAPPED;
  727.   static  const   int32_t             CHARINDEX;  // need look up in .commit()
  728.   static  const   int32_t             EXPANDCHARINDEX; // Expand index follows
  729.   static  const   int32_t             CONTRACTCHARINDEX;  // contract indexes follow
  730.  
  731.   static  const   int32_t             PRIMARYORDERINCREMENT;
  732.   static  const   int32_t             MAXIGNORABLE;
  733.   static  const   int32_t             SECONDARYORDERINCREMENT;
  734.   static  const   int32_t             TERTIARYORDERINCREMENT;
  735.   static  const   int32_t             PRIMARYORDERMASK;
  736.   static  const   int32_t             SECONDARYORDERMASK;
  737.   static  const   int32_t             TERTIARYORDERMASK;
  738.   static  const   int32_t             SECONDARYRESETMASK;
  739.   static  const   int32_t             IGNORABLEMASK;
  740.   static  const   int32_t             PRIMARYDIFFERENCEONLY;
  741.   static  const   int32_t             SECONDARYDIFFERENCEONLY;
  742.   static  const   int32_t             PRIMARYORDERSHIFT;
  743.   static  const   int32_t             SECONDARYORDERSHIFT;
  744.   static  const   int32_t             SORTKEYOFFSET;
  745.   static  const   int32_t             CONTRACTCHAROVERFLOW;
  746.  
  747.   static const int16_t                FILEID;
  748.  
  749.   static       UnicodeString      DEFAULTRULES;
  750.  
  751.   static  const char*             kFilenameSuffix;
  752.  
  753.         //--------------------------------------------------------------------------
  754.         // Data Members
  755.  
  756.   bool_t              isOverIgnore;
  757.   UChar             lastChar;
  758.   MergeCollation*     mPattern;
  759.   UnicodeString       sbuffer;
  760.   UnicodeString       tbuffer;
  761.   UnicodeString       key;
  762.   CollationElementIterator *sourceCursor;
  763.   CollationElementIterator *targetCursor;
  764.   bool_t              dataIsOwned;
  765.   TableCollationData* data;
  766. };
  767.  
  768.  
  769. inline bool_t
  770. RuleBasedCollator::operator!=(const Collator& other) const
  771. {
  772.   return !(*this == other);
  773. }
  774.  
  775. inline void
  776. RuleBasedCollator::addContractOrder(const UnicodeString &groupChars,
  777.                     int32_t                anOrder,
  778.                     UErrorCode            &status)
  779. {
  780.   addContractOrder(groupChars, anOrder, TRUE, status);
  781. }
  782.  
  783. #endif
  784.